#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include "CoreC.h"

uint8_t btn1 = 0;
uint8_t btn1Last = 0;
int btn1StartTime = 0;  //can be a big number!
uint8_t btn2 = 0;
uint8_t btn2Last = 0;
int btn2StartTime = 0;  //can be a big number!

uint8_t PortD_State = 0;
uint8_t _resetSystem = 0;  //flag to indicate if system rest should take place on button release


void HCISetup()
{
  DDRD |= (1<<HCI1 |1<<HCI2); //output
  
  ////Blink LEDs to show they work and system startup
  //uint8_t pins = (1<<LED1 |1<<LED2);
  //blink(pins, 4, blinkSpeed_250, blinkSpeed_250);
}
//
void HCILoop()
{
  
  cli();  // so button states can't be changed and in turn overwritten to old values
  PortD_State = PORTD & (1<<HCI1 |1<<HCI2); //remember led state
  DDRD &= ~(1<<HCI1 |1<<HCI2); //input

  _delay_us(1); //if we don't wait then button 1 is not read correctly
  
  btn1 = PIND & (1<<BUTTON1);
  btn2 = PIND & (1<<BUTTON2);

  DDRD |= (1<<HCI1 |1<<HCI2); //output
  PORTD |= PortD_State; // restore LED state
  sei();

  // ***Button 1 analysis***
  if(btn1 && !btn1Last) //depress
  {
    btn1StartTime = millis();
    //btn1Last = btn1;
  }

  if(!btn1 && btn1Last) //release
  {
    int btn1PressDuration = millis()-btn1StartTime;
    if(btn1PressDuration>50) //ultra quick press ignores for debounce
    {
      if (btn1PressDuration < 2000) //short press
      {
        buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON1_SHORTPRESS;
        buttonData.dataFresh = 1;
      }
      else //long press
      {
        buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON1_LONGPRESS;
        buttonData.dataFresh = 1;
      }
    //uint8_t pins = (1<<LED1 |1<<LED2);
    //blink(pins, 4, blinkSpeed_250, blinkSpeed_250);

    }
   
  }
  
  // ***Button 2 analysis***
  if(btn2 && !btn2Last) //depress
  {
    btn2StartTime = millis();
    //btn2Last = btn2;
  }

  if(!btn2 && btn2Last) //release
  {
    int btn2PressDuration = millis()-btn2StartTime;
    if(btn2PressDuration>50) //ultra quick press ignores for debounce
    {
      if (btn2PressDuration < 2000) //short press
      {
        buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON2_SHORTPRESS;
        buttonData.dataFresh = 1;
        //HCIButton2
      }
      else //long press
      {
        buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON2_LONGPRESS;
        buttonData.dataFresh = 1;
        //
      }
      if (btn2PressDuration > 6000) //very long press
      {
        SystemReset();
      }
      
      
    }

  }
    btn1Last = btn1;
    btn2Last = btn2;  
    //removed because of bugs
  //if (  (btn1 && btn2) && (!(btn1Last)||!(btn2Last))  ) //start of both buttons
  //{
        //btnBothStartTime = millis();
  //}
  //

  //if (  (!(btn1)||!(btn2)) && (btn1Last && btn2Last)  ) //end of both buttons
  //{
        //int btnBothPressDuration = millis()-btnBothStartTime;
        //if(btnBothPressDuration>75) //ultra quick press ignores for debounce
        //{
          //if (btnBothPressDuration < 3000) //short press
          //{
            //buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON1AND2_SHORTPRESS;
            //buttonData.dataFresh = 1;
          //}
          //else //long press
          //{
            //buttonData.btnPressedEvent = HCIDATA_BUTTONPRESSEDEVENT_BUTTON1AND2_LONGPRESS;
            //buttonData.dataFresh = 1;
            //
            //SystemReset();
            ////
          //}
        //}        
  //}
}

// the whole program stops to do this
// do not use inside an interrupt
void blink(uint8_t pin_bits, uint8_t no_of_blinks, uint16_t blinkSpeed_on, uint16_t blinkSpeed_off)
{
  for (uint8_t n = 0;n<no_of_blinks;n++)
  {
    PORTD |= pin_bits;
    _blinkSpeeds(blinkSpeed_on);
    PORTD &= ~pin_bits;
    _blinkSpeeds(blinkSpeed_off);
  }
}
void _blinkSpeeds(uint16_t blinkSpeed)
{
    switch (blinkSpeed)
    {
      case blinkSpeed_50:
      _delay_ms(50);
      break;
      case blinkSpeed_125:
      _delay_ms(125);
      break;
      case blinkSpeed_250:
      _delay_ms(250);
      break;
      case blinkSpeed_500:
      _delay_ms(500);
      break;
      case blinkSpeed_750:
      _delay_ms(750);
      break;
    }
}    